package com.fjd.service.impl;

import com.alibaba.fastjson.JSONObject;
import com.fjd.constant.MessageConstant;
import com.fjd.constant.PayMethodConstant;
import com.fjd.context.BaseContext;
import com.fjd.dto.OrderAddressEditDTO;
import com.fjd.dto.OrderDTO;
import com.fjd.dto.OrderSubmitDTO;
import com.fjd.dto.OrdersPaymentDTO;
import com.fjd.entity.*;
import com.fjd.exception.OrderBusinessException;
import com.fjd.mapper.*;
import com.fjd.service.OrderService;
import com.fjd.utils.WeChatPayUtil;
import com.fjd.vo.AddressVO;
import com.fjd.vo.GoodVO;
import com.fjd.vo.OrderPaymentVO;
import com.fjd.vo.OrderVO;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.math.BigDecimal;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
import java.util.UUID;

@Service
public class OrderServiceImpl implements OrderService {
    @Autowired
    private SalesOrderMapper salesOrderMapper;
    @Autowired
    private SalesDetailMapper salesDetailMapper;
    @Autowired
    private ShoppingProductMapper shoppingProductMapper;
    @Autowired
    private MerchandiseInfoMapper merchandiseInfoMapper;
    @Autowired
    private ProductImageMapper productImageMapper;
    @Autowired
    private CustomerAddrMapper customerAddrMapper;
    @Autowired
    private ProductCategoryMapper productCategoryMapper;
    @Autowired
    private WeChatPayUtil weChatPayUtil;
    @Autowired
    private ShoppingCustomerInfoMapper customerMapper;
    @Autowired
    private DeliveryDetailHistoryMapper deliveryDetailHistoryMapper;
    @Autowired
    private DeliveryDetailMapper deliveryDetailMapper;
    @Autowired
    private DiscountMapper discountMapper;
    @Autowired
    private DiscountDetailMapper discountDetailMapper;


    /**
     * 查询当前用户订单列表
     * @return
     */
    @Transactional
    public List<OrderVO> list(OrderDTO orderDTO) {
        orderDTO.setCustomerId(String.valueOf(BaseContext.getCurrentId()));
        List<OrderVO> orderVOList = salesOrderMapper.list(orderDTO);
        for (OrderVO orderVO : orderVOList) {
            List<Goods> goodsList = FillOrderVOFields(orderVO);
            orderVO.setGoodsList(goodsList);
        }
        return orderVOList;
    }

    @Override
    @Transactional
    public List<GoodVO> submit(List<OrderSubmitDTO> orderSubmitDTOList) {

        //创建一个goodVO的列表
        List<GoodVO> goodVOList = new ArrayList<>();

        //针对每一个传进来的orderSubmitDTO都为其生成一个订单
        for(OrderSubmitDTO osd:orderSubmitDTOList) {
            ShoppingProduct shoppingProduct = shoppingProductMapper.getById(osd.getProductId());

            System.out.println(osd.getProductId());

            //获取该物品的父级商品是否处在打折状态中
            Discount discount = discountMapper.getByMerchandiseIdAndProcessing(shoppingProduct.getParentId());
            BigDecimal amount = new BigDecimal(osd.getAmount().toString());
            BigDecimal totalPrice = shoppingProduct.getPrice().multiply(amount);
            if(discount != null){
                //我勒个长难句啊
                //简单解释就是如果有折扣
                //就找到对应折扣中对应物品的折扣价格
                //然后再和数量相乘获得折扣后的总价格
                totalPrice = discountDetailMapper.getDiscountPriceByProductIdAndDiscountId(shoppingProduct.getProductId(),discount.getId()).getDiscountPrice().multiply(amount);
            }

            //创建一个订单并获取这个订单的单号

            //使用UUID生成一个orderId
            String orderId =UUID.randomUUID().toString().replace("-","");

            SalesOrder salesOrder = SalesOrder.builder()
                    .orderId(orderId)
                    .orderDate(LocalDateTime.now())
                    //设置状态为未付款
                    .orderStatus(SalesOrder.PENDING_PAYMENT)
                    .modifiedDate(LocalDateTime.now())
                    .businessType(osd.getBusinessType())
                    .customerId(BaseContext.getCurrentId())
                    //设置地址：若选择地址则设置其为所选地址，没有设置默认地址为订单地址
                    .addressId(osd.getAddrId() != null
                            ? osd.getAddrId().toString()
                            : customerAddrMapper.getDefaultByCustomerId(BaseContext.getCurrentId()).getAddressId())
                    .referenceId(osd.getReferenceId())
                    .paymentMethod(PayMethodConstant.WECHAT_PAY)
                    //微信支付为3
                    .orderTotal(totalPrice)
                    //c端用户下订单应该用不到这个字段
                    //.lastModifiedBy(BaseContext.getCurrentId().toString())
                    .lastModifiedDate(LocalDateTime.now())
                    .build();
            salesOrderMapper.insert(salesOrder);


            //对sales_detail表插入orderSubmitDTO的数据
            SalesDetail salesDetail = SalesDetail.builder()
                    .orderId(orderId)
                    .productId(shoppingProduct.getProductId())

                    //这个不归商城管 估计后续数据库表表对此项应该设置为可空

                    //2025.03.05更新
                    //仓库地址应该从用户选择的收货地址中最近的仓库进行发货

                    //2025.03.12更新
                    //用于演示 仓库代码写死为000005
                    .warehouseCode("000005")
                    .subtotal( discount!=null?discountDetailMapper.getDiscountPriceByProductIdAndDiscountId(shoppingProduct.getProductId(),discount.getId()).getDiscountPrice():shoppingProduct.getPrice())
                    .productSalesQuantity(osd.getAmount())
                    .totalAmount(totalPrice)
                    .addressId(customerAddrMapper.getDefaultByCustomerId(BaseContext.getCurrentId()).getAddressId())
                    .status(SalesOrder.PENDING_SHIPMEN)
                    .build();

            salesDetailMapper.insert(salesDetail);

            //从product_image表中获取图片集合，将第一张作为GoodVO的图片
            String goodImage = productImageMapper.getByProductId(shoppingProduct.getParentId()).get(0);

            //从merchandise_info表中获取商品名称
            String goodName = merchandiseInfoMapper.getById(shoppingProduct.getParentId()).getMerchandiseName();

            GoodVO goodVO = GoodVO.builder()
                    .imageUrl(goodImage)
                    .merchandiseName(goodName)
                    .priceTotal(totalPrice)
                    .amount(osd.getAmount())
                    .specification(shoppingProduct.getSpecification())
                    .orderId(orderId)
                    .build();

            goodVOList.add(goodVO);

        }

        return goodVOList;
    }

    @Override
    public void cancelOrder(String orderId) {
        //根据id查询订单状态，确定是否可以取消
        SalesOrder order = salesOrderMapper.getById(orderId);
        if(order == null){
            throw new RuntimeException("订单不存在");
        }
        //只有待发货和待付款可以取消
        //改成了equals,!=是对象引用，有bug
        if(!order.getOrderStatus().equals(SalesOrder.PENDING_PAYMENT) && !order.getOrderStatus().equals(SalesOrder.PENDING_SHIPMEN)){
            throw new RuntimeException(MessageConstant.ORDER_STATUS_ERROR_CANCEL);
        }
        //更新订单状态为取消
        salesOrderMapper.updateStatus(orderId, SalesOrder.CANCELLED);
    }


    @Override
    public void editAddress(OrderAddressEditDTO orderAddressEditDTO) {
        String addressId = orderAddressEditDTO.getAddressId();
        System.out.println(addressId);
        String orderId = orderAddressEditDTO.getOrderId();
        salesOrderMapper.setAddress(addressId,orderId);
        salesDetailMapper.setAddress(addressId,orderId);
    }

    @Override
    @Transactional
    public List<GoodVO> again(String orderId) {
        //创建一个goodVO列表
        List<GoodVO> goodVOList = new ArrayList<>();
        //根据orderId查询订单详情
        SalesOrder order = salesOrderMapper.getById(orderId);
        List<SalesDetail> salesDetails = salesDetailMapper.getByOrderId(orderId);
        //创建一个新的订单号
        String Id =UUID.randomUUID().toString().replace("-","");
        //修改细节
        order.setOrderId(Id);
        order.setOrderStatus(SalesOrder.PENDING_PAYMENT);
        order.setModifiedDate(LocalDateTime.now());
        order.setOrderDate(LocalDateTime.now());
        order.setLastModifiedDate(LocalDateTime.now());
        order.setCustomerId(BaseContext.getCurrentId().toString());
        //插入新的订单
        salesOrderMapper.insert(order);
        for (SalesDetail salesDetail : salesDetails) {
            //创建新的订单详情
            salesDetail.setOrderId(Id);
            salesDetailMapper.insert(salesDetail);
            String parentId = productCategoryMapper.getParentNameById(salesDetail.getProductId());
            //从product_image表中获取图片集合，将第一张作为GoodVO的图片
            String goodImage = productImageMapper.getByProductId(parentId).get(0);
            //从merchandise_info表中获取商品名称
            String goodName = merchandiseInfoMapper.getById(parentId).getMerchandiseName();
            GoodVO goodVO = GoodVO.builder()
                    .imageUrl(goodImage)
                    .merchandiseName(goodName)
                    .priceTotal(salesDetail.getTotalAmount())
                    .amount(salesDetail.getProductSalesQuantity())
                    .specification(shoppingProductMapper.getSpecificationById(salesDetail.getProductId()))
                    .orderId(Id)
                    .build();

            goodVOList.add(goodVO);
        }
        return goodVOList;
    }

    @Override
    public OrderVO detail(String orderId) {
        SalesOrder salesOrder = salesOrderMapper.getById(orderId);
        OrderVO orderVO = new OrderVO();
        BeanUtils.copyProperties(salesOrder,orderVO);
        List<Goods> goodsList = FillOrderVOFields(orderVO);
        orderVO.setGoodsList(goodsList);
        return orderVO;
    }

    public List<Goods>  FillOrderVOFields(OrderVO orderVO){
        List<SalesDetail> salesDetailList = salesDetailMapper.getOrderDetail(orderVO.getOrderId());
        List<Goods> goodsList = new ArrayList<>();

        //由于商品表没有具体规格显示，通过物品目录表查询具体规格
        for (SalesDetail sd: salesDetailList){
            Goods goods = new Goods();
            BeanUtils.copyProperties(sd,goods);

            //从product_category表中抽取出购买的商品规格
            ShoppingProduct shoppingProduct = shoppingProductMapper.getById(goods.getProductId());
            goods.setSpecification(shoppingProduct.getSpecification());

            //从merchandise表中抽取出购买的商品名称
            MerchandiseInfo merchandiseInfo = merchandiseInfoMapper.getById(shoppingProduct.getParentId());
            goods.setName(merchandiseInfo.getMerchandiseName());

            //从product_image表中抽取商品对应的图片
            List<String> imageList  = new ArrayList<>();
            imageList = productImageMapper.getByProductId(shoppingProduct.getParentId());
            goods.setImageList(imageList);


            //将商品添加到列表中
            //ps:沟槽的为什么一个冗余字段都没有
            goodsList.add(goods);
        }

        return goodsList;
    }

    @Override
    @Transactional
    public void deleteOrder(String orderId) {
        SalesOrder salesOrder = salesOrderMapper.getById(orderId);
        if (salesOrder.getOrderStatus() == SalesOrder.CANCELLED || salesOrder.getOrderStatus() == SalesOrder.REVIEWED){
            throw new OrderBusinessException(MessageConstant.ORDER_STATUS_ERROR_DELETE);
        }
        salesOrderMapper.deleteById(orderId);
        salesDetailMapper.deleteByOrderId(orderId);
    }

    @Override
    public void confirmOrder(String orderId) {
        SalesOrder salesOrder = salesOrderMapper.getById(orderId);
        if (!Objects.equals(salesOrder.getOrderStatus(), SalesOrder.SHIPPED)){
            throw new OrderBusinessException(MessageConstant.ORDER_STATUS_ERROR);
        }
        salesOrderMapper.updateStatus(orderId,SalesOrder.PENDING_REVIEW);
    }


    public OrderPaymentVO payment(OrdersPaymentDTO ordersPaymentDTO) throws Exception {
        // 当前登录用户id
        String userId = BaseContext.getCurrentId();
        CustomerInfo user = customerMapper.getByOpenId(userId);

        //调用微信支付接口，生成预支付交易单
        JSONObject jsonObject = weChatPayUtil.pay(
                ordersPaymentDTO.getOrderNumber(), //商户订单号
                new BigDecimal(0.01), //支付金额，单位 元
                "冷链商城订单", //商品描述
                user.getOpenId() //微信用户的openid
        );

        if (jsonObject.getString("code") != null && jsonObject.getString("code").equals("ORDERPAID")) {
            throw new OrderBusinessException("该订单已支付");
        }

        OrderPaymentVO vo = jsonObject.toJavaObject(OrderPaymentVO.class);
        vo.setPackageStr(jsonObject.getString("package"));

        return vo;
    }

    public void paySuccess(String outTradeNo) {

        // 根据订单号查询订单
        SalesOrder ordersDB = salesOrderMapper.getById(outTradeNo);

        // 根据订单id更新订单的状态、支付方式、支付状态、支付时间
        SalesOrder orders = SalesOrder.builder()
                .orderId(ordersDB.getOrderId())
                .orderStatus(SalesOrder.PENDING_SHIPMEN)
                .paymentMethod("微信支付")
                .lastModifiedDate(LocalDateTime.now())
                .build();

        salesOrderMapper.update(orders);
    }

    @Override
    public List<DeliveryDetailHistory> deliverydetail(String orderId) {
        String deliveryId = deliveryDetailMapper.select(orderId);
        List<DeliveryDetailHistory> deliveryDetailHistories= deliveryDetailHistoryMapper.select(deliveryId);
        return deliveryDetailHistories;
    }

    @Override
    public AddressVO getOrderAddr(String orderId){
        CustomerAddr addr=customerAddrMapper.getByAddressId(orderId);
        AddressVO addressVO=new AddressVO();
        addressVO.setConsignee(addr.getConsignee());
        addressVO.setPhone(addr.getPhone());
        addressVO.setAddress((addr.getState()+addr.getCity()+addr.getDistrict()+addr.getStreetAddress()).toString());
        return addressVO;
    }

    /**
     * 查询某一个订单
     * @param orderId 订单ID
     * @return 返回订单的详细信息，包括订单和商品列表
     */
    @Transactional
    public OrderVO select(String orderId) {
        // 查询订单信息
        OrderVO orderVO = salesOrderMapper.select(orderId);

        // 获取订单对应的商品明细
        List<SalesDetail> salesDetailList = salesDetailMapper.getOrderDetail(orderVO.getOrderId());
        List<Goods> goodsList = new ArrayList<>();

        // 遍历商品明细，填充商品信息
        for (SalesDetail sd : salesDetailList) {
            Goods goods = new Goods();
            BeanUtils.copyProperties(sd, goods);  // 将销售明细复制到商品对象中

            // 从product_category表中抽取出购买的商品规格
            ShoppingProduct shoppingProduct = shoppingProductMapper.getById(goods.getProductId());
            goods.setSpecification(shoppingProduct.getSpecification());

            // 从merchandise表中抽取出购买的商品名称
            MerchandiseInfo merchandiseInfo = merchandiseInfoMapper.getById(shoppingProduct.getParentId());
            goods.setName(merchandiseInfo.getMerchandiseName());

            // 从product_image表中抽取商品对应的图片
            List<String> imageList = productImageMapper.getByProductId(shoppingProduct.getParentId());
            goods.setImageList(imageList);

            // 将商品添加到商品列表中
            goodsList.add(goods);
        }

        // 将商品列表设置到订单VO中
        orderVO.setGoodsList(goodsList);

        // 返回订单信息，包括商品列表
        return orderVO;
    }

    @Override
    public void payorder(String orderId) {
        salesOrderMapper.updateStatus(orderId,SalesOrder.PENDING_SHIPMEN);
    }
}
